﻿using Fleck;
using Newtonsoft.Json;
using Sunny.UI;
using System;
using System.Collections;
using System.Collections.Generic;
using System.Data;
using System.IO;
using System.Linq;
using System.Net;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
using TemplatesPrint.EntityHandle;

namespace TemplatesPrint.Tools
{
    public class WsServe
    {
        public static HashSet<WebSocketServer> servers = new HashSet<WebSocketServer>();
        public static List<IPAddress> IpList;
        public static IPAddress DefaultIp = IPAddress.Parse("127.0.0.1");
        static IDictionary<string, IWebSocketConnection> SocketList = new Dictionary<string, IWebSocketConnection>();
        public static bool StartSockeListener(string port)
        {
            string hostName = Dns.GetHostName();
            IpList = Dns.GetHostAddresses(hostName).ToList();
            if (!IpList.Contains(DefaultIp))
            {
                IpList.Add(DefaultIp);
            }
            //过滤ipv6的
            IpList = IpList.Where(t=>!t.IsIPv6LinkLocal).OrderBy(t=>t.Address).ToList();
                foreach (var ip in IpList)
            {
                try
                {
                var server = new WebSocketServer(string.Format("ws://{0}:{1}", ip.ToString(), port));//监听本机
                    server.RestartAfterListenError = true;
                    //开始监听
                    server.Start(socket =>
                    {
                        string clientUrl = socket.ConnectionInfo.ClientIpAddress + ":" + socket.ConnectionInfo.ClientPort;
                        socket.OnOpen = () => //连接建立事件
                        {
                            SocketList.Add(clientUrl, socket);
                            WsHandlerTool.OnOpen(clientUrl);
                        };
                        socket.OnClose = () => //连接关闭事件
                        {
                            if (SocketList.ContainsKey(clientUrl))
                            {
                                SocketList.Remove(clientUrl);
                                WsHandlerTool.OnClose(clientUrl);
                            }
                        };
                        socket.OnMessage = message => //接受客户端网页消息事件
                        {
                            WsHandlerTool.OnMessage(clientUrl, message);
                        };
                        socket.OnError = error =>
                        {

                        };
                    });
                    TaskLogHandle.SaveLog("", "开启服务成功", string.Format("ws://{0}:{1}", ip.ToString(), port));
                    servers.Add(server);
                }
                catch (Exception ex)
                {
                    TaskLogHandle.SaveLog("", "开启服务失败", string.Format("ws://{0}:{1}", ip.ToString(), port));
                    continue;
                }
            }
            return true;
           
        }
        //向客户端发送消息
        public static void SendMessage(string client, string msg)
        {
            //msg = msg.Replace("\\\"","\"");
            if (SocketList.ContainsKey(client))
            {
                SocketList[client].Send(msg);
                TaskLogHandle.SaveLog("", "发送信息:"+client, msg);
            }
        }
        public static bool HaveListenerSocket()
        {
            if (servers.Count == 0)
            {
                return false;
            }
            return servers.Any(t => t.ListenerSocket != null);
           
        }
        //关闭与所有客户端的连接
        private static void CloseSocket()
        {
            foreach (var item in SocketList.Values)
            {
                if (item != null)
                {
                    TaskLogHandle.SaveLog("", "关闭服务，断开连接", item.ConnectionInfo.ClientIpAddress + ":" + item.ConnectionInfo.ClientPort.ToString());
                    item.Close();
                   
                }
            }
        }

        public static void CloseServer()
        {
            string info = "";
            CloseSocket();
            if (servers.Count != 0)
            {
                servers.ForEach(server => {
                    info = server.Location;
                    server.Dispose();
                    server = null;
                });
                servers.Clear();
            }
            TaskLogHandle.SaveLog("", "关闭服务", info);
        }
    }
}
